﻿using System;
using System.Collections.Generic;
using System.Data;
using System.Data.SqlClient;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Shapes;
using Wise.Entities;
using Wise.Util;

namespace NHI.Sync.Tools.Forms
{
    /// <summary>
    /// Window_Encrypt.xaml 的交互逻辑
    /// </summary>
    public partial class Window_Encrypt : Window
    {
        public Window_Encrypt()
        {
            InitializeComponent();
            if (MyDbConfig.Current != null && MyDbConfig.Current.目标数据库 != null)
                encryptConnection.Text = MyDbConfig.Current.目标数据库.GetConnectionString();
        }

        private void encryptTable_TextChanged(object sender, TextChangedEventArgs e)
        {
            string tableName = encryptTable.Text.Trim();
            if (string.IsNullOrEmpty(encryptColumns.Text))
            {

                var tbs = MyDbConfig.Current.表映射
                    .Where(x => string.Equals(x.目标表名, tableName, StringComparison.CurrentCultureIgnoreCase))
                    //.Take(1)
                    .ToList();
                if (tbs.Count > 0)
                {
                    var iq = tbs.SelectMany(x => x.字段映射)
                        .Where(x => x != null)
                        .Where(x => x.加密数据)
                        .Select(x => x.新数据库字段)
                        .Distinct();
                    List<string> columns = null;
                    if (!string.IsNullOrEmpty(MyDbConfig.Current.新增字段前缀))
                    {
                        columns = iq.Where(x => !x.StartsWith(MyDbConfig.Current.新增字段前缀))
                            .ToList();
                    }
                    else
                    {
                        columns = iq.ToList();
                    }
                    encryptColumns.Text = string.Join(Environment.NewLine, columns);
                }
            }
        }

        void OnExecute_Click(object o, EventArgs e)
        {
            try
            {
                string 目标表名 = encryptTable.Text.Trim();
                List<string> columns = encryptColumns.Text.Trim()
                    .Split(Environment.NewLine.ToArray())
                    .Select(x => x.Trim())
                    .Where(x => !string.IsNullOrEmpty(x))
                    .ToList();
                if (columns.Count == 0)
                {
                    MessageBox.Show("没有输入要加密的列名");
                    return;
                }
                DataTable _sourceRows = null;
                string connectionString = encryptConnection.Text.Trim();
                using (IDbConnection con = new SqlConnection(connectionString))
                {
                    var table = 表映射.Create表结构(目标表名, con);
                    if (!table._Exists)
                    {
                        MessageBox.Show($"表[{目标表名}]不存在");
                        return;
                    }
                    string 目标表匹配项 = _GetMatcher(table, 目标表名);
                    using (IDbCommand cmd = con.CreateCommand())
                    {
                        cmd.CommandText = $"SELECT {string.Join(",", columns)},{目标表匹配项} AS _PK FROM [{目标表名}]";
                        try
                        {
                            using (IDataReader reader = cmd.ExecuteReader())
                            {
                                _sourceRows = DbHelper.DataReaderToDataTable(reader);
                            }
                        }
                        catch (Exception exp)
                        {
                            throw new Exception(cmd.CommandText, exp);
                        }
                    }
                    for (int i = _sourceRows.Rows.Count - 1; i > 0; --i)
                    {
                        DataRow myRow = _sourceRows.Rows[i];
                        List<string> builder = new List<string>();
                        for (int j = _sourceRows.Columns.Count; j > 0; --j)
                        {
                            var col = _sourceRows.Columns[j];
                            if (!columns.Any(x => string.Equals(x, col.ColumnName, StringComparison.CurrentCultureIgnoreCase)))
                            {
                                continue;
                            }
                            string val = myRow[col].ToString();
                            if (string.IsNullOrEmpty(val) || RegexHelper.IsEncrypted(val))
                            {
                                continue;
                            }
                            builder.Add($"[{col.ColumnName}]='{SecurityHelper.Encrypt(val)}'");
                        }
                        if (builder.Count > 0)
                        {
                            using (IDbCommand cmd = MyDbConfig.Current.SourceConnection.CreateCommand())
                            {
                                cmd.CommandText = $"UPDATE [{目标表名}] SET {string.Join(",", builder)} WHERE {目标表匹配项}='{myRow["_PK"]}'";
                                try
                                {
                                    cmd.ExecuteNonQuery();
                                }
                                catch (Exception exp)
                                {
                                    throw new Exception(cmd.CommandText, exp);
                                }
                            }
                        }

                    }
                }
            }
            catch (Exception exp)
            {
                MessageBox.Show(exp.ToString());
            }


        }
        string _GetMatcher(表结构 _source, string TableName)
        {
            var list = _source.索引.Where(x => x.主键).ToList();
            if (list.Count > 0)
            {
                return string.Join(" + ", list.OrderBy(x => x.索引列).Select(x => $"ISNULL(CONVERT(NVARCHAR(200), [{x.索引列}]),'')"));
            }
            throw new Exception($"表[{TableName}]没有匹配项(主键、唯一键未指定)");
        }
    }
}
